需求:
實現一個Draw程式,可以根據標註類型畫出以下標註
此時如果把這四個功能丟給四個人實作
就會拿到四種完全不同的實作,然後就又會回到昨天的問題
也就是高低階依賴的關係
會這樣的原因是因為底層的lib對於這幾種圖形的畫法就基本不一樣,有些甚至功能不支援
那怎麼辦呢,這時候就要去定義interface
像這樣
import abc
import numpy as np
class GeometryDrawer(abc.ABC):
_width = 1
_color = COLOR.GREEN
@abc.abstractmethod
def draw(self, img: np.ndarray, box: CropBox):
return NotImplemented
@property
def width(self):
return self._width
@width.setter
def width(self, value):
self._width = value
定義出來的時候就相當於團隊簽下一個契約
不管商業邏輯層要怎麼定義,Drawer就是可以使用這些方法
不管底層邏輯有哪些額外方法,這些東西也都是一定要實現的
定好interface之後,就可以把這個任務分發給同事們
只要商業邏輯按照interface call,就一定不會call錯
並且底層也知道該怎麼拆分這些任務
最後code就會長成
drawer.py
class BoundingBox(GeometryDrawer):
def draw(self, img: np.ndarray, box: CropBox):
cv2.rectangle(img, (box.left, box.top), (box.right, box.bottom), self.color, self._width)
class Point(GeometryDrawer):
def draw(self, img: np.ndarray, box: CropBox):
points = chunk(box.coords, 2)
for point in points:
pts = np.array(point,
np.int32)
img = cv2.circle(img, pts, self._width, self.color, -1)
class Polygon(GeometryDrawer):
def draw(self, img: np.ndarray, box: CropBox):
pts = np.array(box.coords,
np.int32)
is_close = True
pts = pts.reshape((-1, 1, 2))
cv2.polylines(img, [pts], is_close, self.color, self.width)
# etc.
解決XD